/*
 * To change this license header, choose License Headers in Project Properties.
 * To change this template file, choose Tools | Templates
 * and open the template in the editor.
 */
package dao;

import java.sql.Statement;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.logging.Level;
import java.util.logging.Logger;
import javax.swing.JOptionPane;
import org.postgresql.jdbc3g.Jdbc3gResultSet;
import org.postgresql.util.PSQLException;

/**
 *
 * @author charles
 */
public class ConexaoBanco {

    private static ConexaoBanco instacia;
    private final String url;
    private final String usuario;
    private final String senha;
    private Connection con;
    private Statement stm;

    private ConexaoBanco() {

        this.url = "jdbc:postgresql://localhost:5432/postgres";
        this.usuario = "postgres";
        this.senha = "admin";

        try {

            Class.forName("org.postgresql.Driver");

            this.con = DriverManager.getConnection(url, usuario, senha);

            System.out.println("Conexão realizada com sucesso.");

            this.stm = con.createStatement();

        } catch (ClassNotFoundException | SQLException e) {
            e.printStackTrace();
        }
    }

    public static ConexaoBanco getInstacia() {

        if (ConexaoBanco.instacia == null) {
            ConexaoBanco.instacia = new ConexaoBanco();
        }

        return ConexaoBanco.instacia;
    }

    public void cadastrarCliente(String nome, String cpf, String rua, String bairro, String cidade, String estado, String telefone, char sexo) {
        System.out.println("entrou");
        System.out.println(nome);
        try {
            System.out.println("INSERT INTO locadora.cliente (nome,cpf,rua,bairro,cidade,estado,telefone,sexo)VALUES ('"
                    + nome + "', '" + cpf + "', '" + rua + "', '" + bairro
                    + "', '" + cidade + "', '" + estado + "', '" + telefone + "', '" + sexo + "')");
            stm.executeQuery("INSERT INTO locadora.cliente (nome,cpf,rua,bairro,cidade,estado,telefone,sexo)VALUES ('"
                    + nome + "', '" + cpf + "', '" + rua + "', '" + bairro
                    + "', '" + cidade + "', '" + estado + "', '" + telefone + "', '" + sexo + "')");
        } catch (SQLException ex) {
            ex.printStackTrace();
        }
    }

    public void cadastrarFilme(String nome, String duracao, String capa, String sinopse, String categoria) {
        ResultSet set;
        try {
            System.out.println("INSERT INTO locadora.filme (nome,duracao,capa,sinopse,categoria)VALUES ('"
                    + nome + "', '" + duracao + "', " + capa + ", '" + sinopse + "', " + categoria + ")");
            set = stm.executeQuery("INSERT INTO locadora.filme (nome,duracao,capa,sinopse,categoria)VALUES ('"
                    + nome + "', '" + duracao + "', '" + capa + "', '" + sinopse + "', '" + categoria + "')");



        } catch (PSQLException e) {
            e.printStackTrace();
            System.out.println("Insercao ocorrida com sucesso!");
        } catch (SQLException ex) {
            ex.printStackTrace();
        }

    }

    public void fecharConexao() {
        try {
            con.close();
        } catch (SQLException ex) {
            ex.printStackTrace();
        }
    }

    public String getIdCategoria(String nome) {
        ResultSet set;
        String result = "";
        try {

            set = stm.executeQuery("SELECT categoria FROM locadora.preco WHERE nome = '" + nome + "'");
            if (!set.next()) {
                System.out.println("Não retornou nada!");
            } else {
                System.out.println(set.getInt("categoria"));
            }
            result += set.getInt("categoria");
            return result;
        } catch (SQLException ex) {
            ex.printStackTrace();

        }
        return null;
    }

    public boolean cadastrarCategoria(String categoria, String preco) {
        ResultSet set;
        try {
            System.out.println("INSERT INTO locadora.preco (categoria,valor)VALUES ('"
                    + categoria + "'," + preco + ")");
            set = stm.executeQuery("INSERT INTO locadora.preco (categoria,valor)VALUES ('"
                    + categoria + "'," + preco + ")");

        } catch (PSQLException e) {

            e.printStackTrace();
            //System.out.println("Insercao ocorrida com sucesso!");
            //JOptionPane.showMessageDialog(null, "Categoria cadastrada com sucesso");
            return true;
        } catch (SQLException ex) {
            ex.printStackTrace();
            return false;
        }
        return false;
    }

    public ArrayList<String> getAllCategoria() {
        //String resultado[] = new String[1000];
        ArrayList<String> resultado = new ArrayList<>();
        ResultSet set;
        try {

            set = stm.executeQuery("SELECT categoria FROM locadora.preco");
            int i = 0;
            while (set.next()) {
                resultado.add(set.getString("categoria"));
                //System.out.println(id);
                // i++;
            }

            return resultado;
        } catch (PSQLException e) {

            e.printStackTrace();
            //System.out.println("Insercao ocorrida com sucesso!");
            //JOptionPane.showMessageDialog(null, "Categoria cadastrada com sucesso");
        } catch (SQLException ex) {
            ex.printStackTrace();
        }
        return null;

    }

    public String getValorCategoria(String categoria) {
        ResultSet set;
        String result = "";
        try {

            set = stm.executeQuery("SELECT valor FROM locadora.preco WHERE categoria = '" + categoria + "'");
            if (!set.next()) {
                //System.out.println("Não retornou nada!");
            } else {
                //System.out.println(set.getInt("valor"));
            }
            result += set.getString("valor");
            return result;
        } catch (SQLException ex) {
            ex.printStackTrace();

        }
        return null;
    }

    /**
     * Metodo geral que insere em qualquer tabela
     *
     * @param schema esquema
     * @param table tabela
     * @param into_values valores especificados no INTO(....)
     * @param values valores especificados no VALUES (...)
     * @return verdadeiro se a insercao teve sucesso caso contrario retorna
     * falso
     */
    public boolean Inserir(String schema, String table, String into_values[], String values[]) {
        String query = "INSERT INTO " + schema + "." + table + " (";
        for (int i = 0; i < into_values.length; i++) {
            if (i == into_values.length - 1) {
                query += into_values[i];
            } else {
                query += into_values[i] + ",";
            }
        }
        query += ") VALUES (";
        for (int i = 0; i < values.length; i++) {
            if (i == values.length - 1) {
                query += "'" + values[i] + "'";
            } else {
                query += "'" + values[i] + "',";
            }
        }
        query += ")";
        System.out.println("QUERY: " + query);

        ResultSet set;
        try {
            set = stm.executeQuery(query);
        } catch (PSQLException e) {
            JOptionPane.showMessageDialog(null, e.toString());

            //System.out.println("Insercao ocorrida com sucesso!");
            //JOptionPane.showMessageDialog(null, "Categoria cadastrada com sucesso");
            return true;
        } catch (SQLException ex) {
            JOptionPane.showMessageDialog(null, ex.toString());

            return false;
        }

        return true;
    }

    public String InserirReturning(String schema, String table, String into_values[], String values[], String retorno) {
        String query = "INSERT INTO " + schema + "." + table + " (";
        for (int i = 0; i < into_values.length; i++) {
            if (i == into_values.length - 1) {
                query += into_values[i];
            } else {
                query += into_values[i] + ",";
            }
        }
        query += ") VALUES (";
        for (int i = 0; i < values.length; i++) {
            if (i == values.length - 1) {
                query += "'" + values[i] + "'";
            } else {
                query += "'" + values[i] + "',";
            }
        }
        query += ") RETURNING " + retorno;
        System.out.println("QUERY: " + query);

        ResultSet set;
        try {
            set = stm.executeQuery(query);
            return set.getString(retorno);
        } catch (PSQLException e) {

            e.printStackTrace();
            //System.out.println("Insercao ocorrida com sucesso!");
            //JOptionPane.showMessageDialog(null, "Categoria cadastrada com sucesso");
        } catch (SQLException ex) {
            ex.printStackTrace();

        }

        return null;
    }

    public String[][] Select(String select[], String from[], String on[], String where[], String type) {
        String query = "SELECT ";
        String query2 = "SELECT count(*)";

        for (int i = 0; i < select.length; i++) {
            if (i == select.length - 1) {
                query += select[i];
            } else {
                query += select[i] + ", ";
            }
        }

        query += " FROM ";
        query2 += " FROM ";

        //teste de sanidade
        if (from.length >= 2) {
            query += from[0] + " " + type + " " + from[1];
            query2 += from[0] + " " + type + " " + from[1];
            if (on != null) {
                query += " ON(" + on[0] + ") ";
                query2 += " ON(" + on[0] + ") ";
            }
            for (int i = 2; i < from.length; i++) {
                if (i == from.length - 1) {
                    query += " " + type + " " + from[i];
                    query2 += " " + type + " " + from[i];
                } else {
                    //query += from[i] + " " + type + " ";
                    //query2 += from[i] + " " + type + " ";
                    query += " " + type + " " + from[i];
                    query2 += " " + type + " " + from[i];
                    if (on != null) {
                        query += " ON(" + on[i - 1] + ") ";
                        query2 += " ON(" + on[i - 1] + ") ";
                    }
                }
            }
        } else {
            query += from[0];
            query2 += from[0];
        }
        if (from.length > 2) {
            if (on != null) {
                query += " ON(" + on[on.length - 1] + ") ";
                query2 += " ON(" + on[on.length - 1] + ") ";
            }
        }
        if (where != null) {
            query += " WHERE ";
            query2 += " WHERE ";
            //só faz com and..
            for (int i = 0; i < where.length; i++) {
                if (i == where.length - 1) {
                    query += where[i];
                    query2 += where[i];
                } else {
                    query += where[i] + " and ";
                    query2 += where[i] + " and ";
                }
            }
        }
        System.out.println("RESULTADO: " + query);
        ResultSet set, set2;
        int tamanho = 0;
        try {
            set = stm.executeQuery(query2);
            while (set.next()) {
                tamanho = set.getInt("count");
                System.out.println("tamanho(linhas) é: " + tamanho);
            }
            String[][] resultado = new String[tamanho][select.length];
            set.close();
            set2 = stm.executeQuery(query);
            int i = 0, j = 0;
            while (set2.next()) {
                j = 0;
                while (j < select.length) {
                    //String aux_select[];
//                    if (select[j].contains("as")) {
//
//                        String aux_select[] = select[j].split("as");
//                        System.out.println("select[1]: " + select[1]);
//                        resultado[i][j] = set2.getString(aux_select[1]);
//                        
//                        
//                    } else {
//                        resultado[i][j] = set2.getString(select[j]);
//                    }

                    resultado[i][j] = set2.getString(j + 1);
                    //resultado[i][j] = set2.getString(select[j]);
                    j++;
                }
                i++;
            }

            for (String[] strings : resultado) {
                for (String string : strings) {
                    System.out.println("Resultado: " + string);
                }
            }

            return resultado;

            //set2 = stm.executeQuery(query);
        } catch (PSQLException e) {
            e.printStackTrace();
            return null;
        } catch (SQLException ex) {
            ex.printStackTrace();
            return null;
        }

    }

    /**
     * Modifica um atributo da tabela
     *
     * @param schema nome do schema
     * @param table nome da tabela
     * @param set variaveis a serem modificadas
     * @param values valores a serem colocados na tabela a ser modificada
     * @param where condicao
     * @return true se foi possiver modificar e false se houver algum erro
     */
    public boolean Update(String schema, String table, String set[], String values[], String where[]) {
        String query = "UPDATE " + schema + "." + table + " ";
        for (int i = 0; i < set.length; i++) {
            if (i == set.length - 1) {
                query += set[i];
            } else {
                query += set[i] + " = " + values[i];
            }
        }
        query += " WHERE ";
        for (int i = 0; i < where.length; i++) {
            if (i == where.length - 1) {
                query += where[i];
            } else {
                query += where[i] + " and ";
            }
        }

        System.out.println("QUERY: " + query);

        ResultSet resultset;
        try {
            resultset = stm.executeQuery(query);
        } catch (PSQLException e) {

            e.printStackTrace();
            return true;
        } catch (SQLException ex) {
            ex.printStackTrace();
            return false;
        }

        return true;
    }

    public String[][] getDataFilm(String s, String type) {
        //ArrayList <String> resultado = new ArrayList<>();
        ResultSet set, set2;
        int tamanho = 0;
        try {

            set = stm.executeQuery("SELECT filme.id_filme,filme.nome,filme.ano_lancamento,count(copia.id_copia)\n"
                    + "FROM locadora.filme " + type + " locadora.copia ON (filme.id_filme=copia.id_filme)\n"
                    + "WHERE nome LIKE '%" + s + "%'"
                    + "GROUP BY filme.id_filme");

            while (set.next()) {
                tamanho++;
            }
            System.out.println("tamanho(linhas) é: " + tamanho);
            String[][] resultado = new String[tamanho][4];

            set2 = stm.executeQuery("SELECT filme.id_filme,filme.nome,filme.ano_lancamento,count(copia.id_copia)\n"
                    + "FROM locadora.filme" + type + " locadora.copia ON (filme.id_filme=copia.id_filme)\n"
                    + "WHERE nome LIKE '%" + s + "%' "
                    + "GROUP BY filme.id_filme");
            int i = 0;
            while (set2.next()) {
                //resultado.add(set.getString("categoria"));
                //System.out.println(id);
                resultado[i][0] = set2.getString("id_filme");
                resultado[i][1] = set2.getString("nome");
                resultado[i][2] = set2.getString("ano_lancamento");
                resultado[i][3] = set2.getString("count");

                i++;
            }

            for (int j = 0; j < tamanho; j++) {
                System.out.println();
                for (int k = 0; k < 4; k++) {
                    System.out.print(resultado[j][k] + " ");

                }


            }

            return resultado;
        } catch (PSQLException e) {

            e.printStackTrace();
            //System.out.println("Insercao ocorrida com sucesso!");
            //JOptionPane.showMessageDialog(null, "Categoria cadastrada com sucesso");
        } catch (SQLException ex) {
            ex.printStackTrace();
        }
        return null;
    }

    public String[][] BuscaFilme(String nome) {

        ResultSet set, set2;
        int tamanho = 0;
        try {

            set2 = stm.executeQuery("SELECT count(*) FROM locadora.filme WHERE nome LIKE '%" + nome + "%'");
            while (set2.next()) {
                tamanho = set2.getInt("count");
                System.out.println("tamanho(linhas) é: " + tamanho);
            }
            set = stm.executeQuery("SELECT id_filme,nome,ano_lancamento FROM locadora.filme WHERE nome LIKE '%" + nome + "%'");
            int i = 0;
            String[][] resultado = new String[tamanho][3];
            while (set.next()) {
                //resultado.add(set.getString("categoria"));
                //System.out.println(id);
                resultado[i][0] = set.getString("id_filme");
                resultado[i][1] = set.getString("nome");
                resultado[i][2] = set.getString("ano_lancamento");
                i++;
            }

            for (int j = 0; j < tamanho; j++) {
                System.out.println();
                for (int k = 0; k < 3; k++) {
                    System.out.print(resultado[j][k] + " ");

                }
            }

            return resultado;
        } catch (PSQLException e) {

            e.printStackTrace();
            //System.out.println("Insercao ocorrida com sucesso!");
            //JOptionPane.showMessageDialog(null, "Categoria cadastrada com sucesso");
        } catch (SQLException ex) {
            ex.printStackTrace();
        }
        return null;


    }

    public String[] filmeDetails(String idfilme) throws Exception {
        throw new Exception("Não implementado ainda");
    }

    public String returningId(String r) {
        String query = "RETURNING " + r;
        ResultSet set;
        //int tamanho = 0;
        try {

            set = stm.executeQuery(query);
            System.out.println(set.getInt(r));
        } catch (PSQLException e) {

            e.printStackTrace();
            //System.out.println("Insercao ocorrida com sucesso!");
            //JOptionPane.showMessageDialog(null, "Categoria cadastrada com sucesso");
        } catch (SQLException ex) {
            ex.printStackTrace();
        }
        return null;



    }

    public void delete(String from, String where[]) {
        String query = "DELETE FROM " + from + " ";
        ResultSet set;


        query += " WHERE ";
        for (int i = 0; i < where.length; i++) {
            if (i == where.length - 1) {
                query += where[i];
            } else {
                query += where[i] + " and ";
            }
        }
        try {
            System.out.println("query delete: " + query);
            set = stm.executeQuery(query);
            //System.out.println(set.getInt(query));
        } catch (PSQLException e) {

            e.printStackTrace();
            //System.out.println("Insercao ocorrida com sucesso!");
            //JOptionPane.showMessageDialog(null, "Categoria cadastrada com sucesso");
        } catch (SQLException ex) {
            ex.printStackTrace();
        }
        //return null;

    }

    public void update(String from, String set[], String where[]) {
        String query = "UPDATE " + from + " SET ";
        ResultSet set1;

        for (int i = 0; i < set.length; i++) {
            if (i == set.length - 1) {
                query += set[i];
            } else {
                query += set[i] + ", ";
            }
        }

        query += " WHERE ";
        for (int i = 0; i < where.length; i++) {
            if (i == where.length - 1) {
                query += where[i];
            } else {
                query += where[i] + " and ";
            }
        }
        try {
            System.out.println("query update: " + query);
            set1 = stm.executeQuery(query);
            //System.out.println(set.getInt(query));
        } catch (PSQLException e) {

            e.printStackTrace();
            //System.out.println("Insercao ocorrida com sucesso!");
            //JOptionPane.showMessageDialog(null, "Categoria cadastrada com sucesso");
        } catch (SQLException ex) {
            ex.printStackTrace();
        }
        //return null;

    }
//    public void conectarBD() {
//        try {
//
//            String url = "jdbc:postgresql://localhost:5432/postgres";
//            String usuario = "postgres";
//            String senha = "admin";
//
//            Class.forName("org.postgresql.Driver");
//
//            Connection con;
//
//            con = DriverManager.getConnection(url, usuario, senha);
//
//            System.out.println("Conexão realizada com sucesso.");
//
//            Statement stm = con.createStatement();
//
//            // stm.executeQuery("INSERT INTO teste VALUES (1,'Cynthia')");  
//            //stm.executeUpdate("INSERT INTO teste VALUES (1,'Cynthia')");
//            //Editado 21/09/2011 para correção: executeQuery é usado para pesquisa, executeUpdate deve ser usado para inserir  
//            con.close();
//
//        } catch (ClassNotFoundException | SQLException e) {
//            e.printStackTrace();
//        }
//    }
}
